﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Web.Http;
using AutoMapper;
using TestWebApp.DataAccess.Common;
using TestWebApp.DataAccess.Models;
using TestWebApp.Models;

namespace TestWebApp.Controllers
{
    // TODO: Tests
    // TODO: Add BusinessLogic layer if logic will grow
    public class EmployeesController : ApiController
    {
        private readonly IRepository<Employee> _employeeRepository;

        public EmployeesController(IRepository<Employee> employeeRepository)
        {
            _employeeRepository = employeeRepository;
        }

        public IEnumerable<Employee> GetAll()
        {
            IEnumerable<Employee> employeeList = Enumerable.Empty<Employee>();

            try
            {
                employeeList = _employeeRepository.GetAll();
            }
            catch (Exception e)
            {
                // Log ex.
            }

            return employeeList;
        }

        public Employee Get(int id)
        {
            Employee employee = null;

            try
            {
                employee = _employeeRepository.GetById(id);
            }
            catch (Exception e)
            {
                // Log ex.
            }

            return employee;
        }

        [HttpGet]
        public RemoteValidationResponseModel ValidateEmployeeByEmail(string value)
        {
            var remValRes = new RemoteValidationResponseModel { isValid = true };

            try
            {
                // Implement GetByEmail, instead of getting all entities and filter them in memory
                var employee = _employeeRepository.GetAll().FirstOrDefault(emp => emp.Email == value);
                if (employee != null)
                {
                    remValRes.isValid = false;
                    remValRes.value = value;
                }
            }
            catch (Exception e)
            {
                // Log ex.
            }

            return remValRes;
        }

        [HttpGet]
        public RemoteValidationResponseModel ValidateEmployeeByEmpNumber(string value)
        {
            var remValRes = new RemoteValidationResponseModel { isValid = true };

            try
            {
                // Implement GetByEmpNum, instead of getting all entities and filter them in memory
                var employee = _employeeRepository.GetAll().FirstOrDefault(emp => emp.EmpNumber == int.Parse(value));
                if (employee != null)
                {
                    remValRes.isValid = false;
                    remValRes.value = value;
                }
            }
            catch (Exception e)
            {
                // Log ex.
            }

            return remValRes;
        }

        public HttpResponseMessage Post(EmployeeModel employeeModel)
        {
            if (!ModelState.IsValid)
            {
                return Request.CreateErrorResponse(HttpStatusCode.BadRequest, "Invalid input data");
            }

            var destModel = Mapper.Map<EmployeeModel, Employee>(employeeModel);

            var employee = new Employee();

            try
            {
                // using _employeeRepository.GetById(id) on update throws exception
                employee = _employeeRepository.GetAll().FirstOrDefault(emp => emp.Id == employeeModel.Id) == null
                    ? _employeeRepository.Insert(destModel)
                    : _employeeRepository.Update(destModel);
                _employeeRepository.Save();
            }
            catch (Exception e)
            {
                return Request.CreateErrorResponse(HttpStatusCode.InternalServerError,
                    "Error. Please contact to administrator");
            }

            return Request.CreateResponse(HttpStatusCode.Created, employee);
        }

        public HttpResponseMessage Delete([FromUri]EmployeeModel employeeModel)
        {
            if (!ModelState.IsValid)
            {
                return Request.CreateErrorResponse(HttpStatusCode.BadRequest, "Invalid input data");
            }

            var destModel = Mapper.Map<EmployeeModel, Employee>(employeeModel);

            try
            {
                _employeeRepository.Attach(destModel);
                _employeeRepository.Delete(destModel);
                _employeeRepository.Save();
            }
            catch (Exception e)
            {
                return Request.CreateErrorResponse(HttpStatusCode.InternalServerError,
                    "Error. Please contact to administrator");
            }

            return new HttpResponseMessage(HttpStatusCode.OK);
        }
    }
}
